﻿using System;
using System.Collections.Generic;
using System.Drawing;
using System.Drawing.Drawing2D;
using System.Drawing.Imaging;
using System.IO;
using System.Linq;
using System.Runtime.InteropServices;
using System.Text;
using Common;

namespace ImageProcessor
{
    public class ImageWorker
    {
        public ImageWorker()
        {
            
        }

        public System.Drawing.Image CropImage(System.Drawing.Image Image, int Height, int Width)
        {
            return CropImage(Image, Height, Width, 0, 0);
        }

        //The crop image sub
        public System.Drawing.Image CropImage(System.Drawing.Image Image, int Height, int Width, int StartAtX, int StartAtY)
        {
            Image outimage;
            MemoryStream mm = null;
            try
            {
                //check the image height against our desired image height
                if (Image.Height < Height)
                {
                    Height = Image.Height;
                }

                if (Image.Width < Width)
                {
                    Width = Image.Width;
                }

                //create a bitmap window for cropping
                Bitmap bmPhoto = new Bitmap(Width, Height, PixelFormat.Format24bppRgb);
                bmPhoto.SetResolution(72, 72);

                //create a new graphics object from our image and set properties
                Graphics grPhoto = Graphics.FromImage(bmPhoto);
                grPhoto.SmoothingMode = SmoothingMode.AntiAlias;
                grPhoto.InterpolationMode = InterpolationMode.HighQualityBicubic;
                grPhoto.PixelOffsetMode = PixelOffsetMode.HighQuality;

                //now do the crop
                grPhoto.DrawImage(Image, new Rectangle(0, 0, Width, Height), StartAtX, StartAtY, Width, Height, GraphicsUnit.Pixel);

                // Save out to memory and get an image from it to send back out the method.
                mm = new MemoryStream();
                bmPhoto.Save(mm, System.Drawing.Imaging.ImageFormat.Jpeg);
                Image.Dispose();
                bmPhoto.Dispose();
                grPhoto.Dispose();
                outimage = Image.FromStream(mm);

                return outimage;
            }
            catch (Exception ex)
            {
                throw new Exception("Error cropping image, the error was: " + ex.Message);
            }
        }

        public string SaveImage(Image bitmap, string imageTartgetPath)
        {
            bitmap.Save(imageTartgetPath, ImageFormat.Tiff);
            return imageTartgetPath;
        }

        public Bitmap Grayscale(Bitmap bitmap)
        {
            //Declare myBitmap as a new Bitmap with the same Width & Height
            Bitmap myBitmap = new Bitmap(bitmap.Width, bitmap.Height);

            for (int i = 0; i < bitmap.Width; i++)
            {
                for (int x = 0; x < bitmap.Height; x++)
                {
                    //Get the Pixel 
                    Color BitmapColor = bitmap.GetPixel(i, x);
                    //I want to come back here at some point and understand, then change, the constants
                    //Declare grayScale as the Grayscale Pixel
                    int grayScale = (int)((BitmapColor.R * 0.3) + (BitmapColor.G * 0.59) + (BitmapColor.B * 0.11));

                    //Declare myColor as a Grayscale Color
                    Color myColor = Color.FromArgb(grayScale, grayScale, grayScale);

                    //Set the Grayscale Pixel
                    myBitmap.SetPixel(i, x, myColor);
                }
            }

            ApplyInvert(myBitmap);

            return myBitmap;
        }

        public void ApplyInvert(Bitmap bitmapImage)
        {
            byte A, R, G, B;
            Color pixelColor;

            for (int y = 0; y < bitmapImage.Height; y++)
            {
                for (int x = 0; x < bitmapImage.Width; x++)
                {
                    pixelColor = bitmapImage.GetPixel(x, y);
                    A = pixelColor.A;
                    R = (byte)(255 - pixelColor.R);
                    G = (byte)(255 - pixelColor.G);
                    B = (byte)(255 - pixelColor.B);
                    bitmapImage.SetPixel(x, y, Color.FromArgb((int)A, (int)R, (int)G, (int)B));
                }
            }

        }

        internal void SetBackgroundToWhite(Bitmap bmp)
        {
            for (int i = 1; i < bmp.Height; i++)
            {
                for (int j = 1; j < bmp.Width; j++)
                {
                    if ((bmp.GetPixel(j, i).R > 100) && (bmp.GetPixel(j, i).G > 100) && (bmp.GetPixel(j, i).B > 100))
                    {
                        bmp.SetPixel(j, i, Color.White);
                    }
                    else
                    {
                        bmp.SetPixel(j, i, Color.Black);
                    }
                }
            }
        }


        public Bitmap ResizeBitmap(Bitmap sourceBMP, int width, int height)
        {
            Bitmap result = new Bitmap(width, height);
            using (Graphics g = Graphics.FromImage(result))
                g.DrawImage(sourceBMP, 0, 0, width, height);
            return result;
        }

    }
}
